<?php
namespace app\api\service;

use app\api\model\store\Order as OrderModel;
use app\api\model\user\User as UserModel;

use think\Loader;
use think\Log;

Loader::import('WxPay.WxPay', EXTEND_PATH, '.Api.php');

class Pay{

    private $mOrderModel = Null;
    private $mUserModel = NULL;

    private $configData = null;

    function __construct(){
        $this->mOrderModel = new OrderModel();
        $this->mUserModel = new UserModel();

        $this->configData = [
            'appid' => config('wx.appid'),
            'mch_id' => config('wx.mch_id'),
            'sub_appid' => config('wx.app_id'),
            'sub_mch_id' => config('wx.sub_mch_id'),
        ];
    }

    public function pay($orderID = 0, $type = 0){
        if (!$orderID) {
            throwError('支付失败，请联系管理员1!', $orderID);
        }
        $order = $this->mOrderModel->findDataByID($orderID);
        if(!$order) {
            throwError('支付失败，请联系管理员2!');
        }

        if($order['order_status'] != 0){
            throwError('支付失败，请联系管理员3!');
        }
        $userId = $order['user_id'];

        $user = $this->mUserModel->findDataByID($userId);

        if (!$user) {
            throwError('用户不存在!');
        }
        if (!$user['open_id']) {
            throwError('暂未登录!');
        }

        return $this->makeWxPreOrder($order, $user['open_id'], $type);
    }

    // 构建微信支付订单信息
    private function makeWxPreOrder($order, $openid, $type){
        //$totalPrice = $order['pay_price'];//实付
        $totalPrice = 0.01;//1分
        $out_trade_no = $order['order_no'];
        $wxOrderData = new \WxPayUnifiedOrder();

        $wxOrderData->SetAppid($this->configData['appid']);//服务商商户的小程序ID（APPID）
        $wxOrderData->SetMch_id($this->configData['mch_id']);//服务商商户号

        $wxOrderData->SetSub_appid($this->configData['sub_appid']);//特约商户的小程序ID
        $wxOrderData->SetSub_mch_id($this->configData['sub_mch_id']);//特约商户号

        $wxOrderData->SetOut_trade_no($out_trade_no);
        $wxOrderData->SetTrade_type('JSAPI');
        $wxOrderData->SetTotal_fee($totalPrice * 100);
        $wxOrderData->SetBody('丽湾饰品');
        //$wxOrderData->SetOpenid($openid);
        $wxOrderData->SetSub_openid($openid);
        $wxOrderData->SetNotify_url(config('secure.pay_back_url'));
        return $this->getPaySignature($wxOrderData, $order['id'], $type);
    }

    //向微信请求订单号并生成签名
    private function getPaySignature($wxOrderData, $orderID, $type = 0)
    {
        $wxOrder = \WxPayApi::unifiedOrder($wxOrderData, 6, $type);
        //Log::record($wxOrder, 'wxOrder');

        // 失败时不会返回 result_code
        if ($wxOrder['return_code'] != 'SUCCESS' || $wxOrder['result_code'] != 'SUCCESS') {
            //throwError('支付失败，请联系管理员!');
            throwError($wxOrder['err_code_des']);
        }
        //$this->recordPreOrder($wxOrder, $orderID);
        $signature = $this->sign($wxOrder);
        return $signature;
    }

    private function recordPreOrder($wxOrder, $orderID){
        // 必须是update，每次用户取消支付后再次对同一订单支付，prepay_id是不同的
        $this->mOrderModel->where('id', '=', $orderID)->update(['prepay_id' => $wxOrder['prepay_id']]);
    }

    // 签名
    private function sign($wxOrder)
    {
        $jsApiPayData = new \WxPayJsApiPay();
        $jsApiPayData->SetAppid(config('wx.app_id'));
        $jsApiPayData->SetTimeStamp((string)time());
        $rand = md5(time() . mt_rand(0, 1000));
        $jsApiPayData->SetNonceStr($rand);
        $jsApiPayData->SetPackage('prepay_id=' . $wxOrder['prepay_id']);
        $jsApiPayData->SetSignType('md5');
        $sign = $jsApiPayData->MakeSign();
        $rawValues = $jsApiPayData->GetValues();
        $rawValues['paySign'] = $sign;
        unset($rawValues['appId']);
        return $rawValues;
    }

}